package com.ecoolex.ying.space.core.manager;

import com.ecoolex.framework.common.enums.ResultCode;
import com.ecoolex.framework.common.pojo.Page;
import com.ecoolex.framework.common.pojo.Pagination;
import com.ecoolex.framework.common.pojo.Sorting;
import com.ecoolex.framework.common.pojo.Sortings;
import com.ecoolex.framework.common.util.BizAssert;
import com.ecoolex.framework.common.util.Check;
import com.ecoolex.framework.common.util.CollectorUtil;
import com.ecoolex.framework.common.util.io.HttpUtil;
import com.ecoolex.ying.space.core.dao.UserWorksShoppingDAO;
import com.ecoolex.ying.space.entity.UserWorks;
import com.ecoolex.ying.space.entity.UserWorksImages;
import com.ecoolex.ying.space.entity.UserWorksShopping;
import com.ecoolex.ying.space.entity.UserWorksShopping.Column;
import com.ecoolex.ying.space.entity.UserWorksShoppingExample;
import com.ecoolex.ying.space.entity.UserWorksShoppingExample.Criteria;
import com.ecoolex.ying.space.enums.UserWorksShoppingType;
import com.ecoolex.ying.space.enums.UserWorksType;
import com.ecoolex.ying.space.pojo.AddUserWorksShoppingsDTO;
import com.ecoolex.ying.space.pojo.QueryShopWindowGoodsDTO;
import com.google.common.collect.Lists;

import java.sql.Date;
import java.time.Instant;
import java.util.List;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;


@Service
public class UserWorksShoppingManager {

    @Autowired
    private UserWorksShoppingDAO dao;

    public void verify(AddUserWorksShoppingsDTO dto, UserWorks userWorks, String storageId) {
        List<UserWorksShopping> oldList = queryByStorageId(storageId);
        BizAssert.isTrue(Check.notNullAndGtZero(dto.getType()), ResultCode.VERIFY.build(11), "用户作品购物类型为空");
//        if (Check.notNullOrTrimEmpty(dto.getLabel())) {
//            for (UserWorksShopping userWorksShopping : oldList) {
//                BizAssert.isFlase(dto.getLabel().equals(userWorksShopping.getLabel()),
//                    ResultCode.VERIFY.build(12),
//                    "标签={}已存在",
//                    dto.getLabel());
//            }
//        }
//        if (dto.getType() == UserWorksShoppingType.GOODS.real()) {
//            BizAssert.isTrue(Check.notNullAndGtZero(dto.getGoodsId()), ResultCode.VERIFY.build(13), "商品id为空");
//            for (UserWorksShopping userWorksShopping : oldList) {
//                BizAssert.isFlase(dto.getGoodsId().equals(userWorksShopping.getGoodsId()),
//                    ResultCode.VERIFY.build(14),
//                    "商品={}已存在",
//                    dto.getGoodsId());
//            }
//        }
//        if (dto.getType() == UserWorksShoppingType.PACKAGE.real()) {
//            BizAssert.isTrue(Check.notNullAndGtZero(dto.getPackagedId()), ResultCode.VERIFY.build(15), "套餐id为空");
//            for (UserWorksShopping userWorksShopping : oldList) {
//                BizAssert.isFlase(dto.getPackagedId().equals(userWorksShopping.getPackagedId()),
//                    ResultCode.VERIFY.build(16),
//                    "套餐={}已存在",
//                    dto.getPackagedId());
//            }
//        }
        if (dto.getType() == UserWorksShoppingType.LINK.real()) {
            BizAssert.isTrue(Check.notNullOrTrimEmpty(dto.getLink()), ResultCode.VERIFY.build(17), "链接为空");
            BizAssert.isTrue(Check.notNullOrTrimEmpty(dto.getLinkName()), ResultCode.VERIFY.build(18), "链接名称为空");
        }
    }

    public List<UserWorksShopping> updateUserWorksShopping(UserWorks userWorks, String storageId, List<AddUserWorksShoppingsDTO> dtoList, String createUser) {
        List<UserWorksShopping> oldList = queryByStorageId(storageId);
        List<UserWorksShopping> result = Lists.newArrayList();
        if (Check.notNullOrEmpty(dtoList)) {
            for (int i = 0; i < dtoList.size(); i++) {
                AddUserWorksShoppingsDTO dto = dtoList.get(i);
                verify(dtoList.get(i), userWorks, storageId);
                // 编辑
                if (Check.notNull(dto.getId())) {
                    UserWorksShopping old
                        = oldList.stream().collect(CollectorUtil.first(o -> dto.getId().equals(o.getId())));
                    BizAssert.isTrue(Check.notNull(old), ResultCode.VERIFY.build(30), "作品购物标签={}不存在", dto.getId());

                    if (dto.getType() == UserWorksShoppingType.GOODS.real()) {
                        old.setGoodsId(dto.getGoodsId());
                    }
                    if (dto.getType() == UserWorksShoppingType.PACKAGE.real()) {
                        old.setPackagedId(dto.getPackagedId());
                    }
                    if (dto.getType() == UserWorksShoppingType.LINK.real()) {
                        BizAssert.isTrue(HttpUtil.isHttpUrl(dto.getLink()), ResultCode.VERIFY.build(31), "链接无效");
                        old.setLink(dto.getLink());
                        old.setLinkName(dto.getLinkName());
                        old.setLinkPrice(dto.getLinkPrice());
                    }
                    if (userWorks.getWorksType() == UserWorksType.IMAGES.real()
                        || userWorks.getWorksType() == UserWorksType.OPUS.real()) {
                        old.setLabel(dto.getLabel());
                    }
                    old.setOrdered(i + 1);
                    old.setStorageId(storageId);
                    old.setType(dto.getType());
                    old.setUserId(userWorks.getUserId());
                    old.setWorksId(userWorks.getWorksId());
                    old.setUpdateUser(createUser);
                    old.setUpdateTime(Date.from(Instant.now()));
                    dao.updateByPrimaryKeySelective(old,
                        Column.excludes(Column.deleted, Column.createTime, Column.createUser));
                    // 移除
                    oldList.remove(old);
                    result.add(old);
                } else {// 新增
                    UserWorksShopping userWorksShopping = new UserWorksShopping();
                    if (dto.getType() == UserWorksShoppingType.GOODS.real()) {
                        userWorksShopping.setGoodsId(dto.getGoodsId());
                    }
                    if (dto.getType() == UserWorksShoppingType.PACKAGE.real()) {
                        userWorksShopping.setPackagedId(dto.getPackagedId());
                    }
                    if (dto.getType() == UserWorksShoppingType.LINK.real()) {
                        BizAssert.isTrue(HttpUtil.isHttpUrl(dto.getLink()), ResultCode.VERIFY.build(32), "链接无效");
                        userWorksShopping.setLink(dto.getLink());
                        userWorksShopping.setLinkName(dto.getLinkName());
                        userWorksShopping.setLinkPrice(dto.getLinkPrice());
                    }
                    if (userWorks.getWorksType() == UserWorksType.IMAGES.real()
                        || userWorks.getWorksType() == UserWorksType.OPUS.real()) {
                        userWorksShopping.setLabel(dto.getLabel());
                    }
                    userWorksShopping.setOrdered(i + 1);
                    userWorksShopping.setType(dto.getType());
                    userWorksShopping.setStorageId(storageId);
                    userWorksShopping.setUserId(userWorks.getUserId());
                    userWorksShopping.setWorksId(userWorks.getWorksId());

                    userWorksShopping.setDeleted(UserWorksImages.NOT_DELETED);
                    userWorksShopping.setCreateUser(createUser);
                    userWorksShopping.setCreateTime(Date.from(Instant.now()));
                    userWorksShopping.setUpdateUser(createUser);
                    userWorksShopping.setUpdateTime(Date.from(Instant.now()));

                    dao.insert(userWorksShopping);
                    dto.setId(userWorksShopping.getId());
                    result.add(userWorksShopping);

                }
            }
            // 删除多余的
            oldList.forEach(old -> delete(old, createUser));
        } else {
            for (UserWorksShopping userWorksShopping : oldList) {
                userWorksShopping.setDeleted(UserWorksShopping.IS_DELETED);
                userWorksShopping.setUpdateUser(createUser);
                userWorksShopping.setUpdateTime(Date.from(Instant.now()));
                dao.updateByPrimaryKey(userWorksShopping);
            }
        }
        return result;
    }

    public List<UserWorksShopping> queryByWorksId(Integer worksId) {
        UserWorksShoppingExample example = new UserWorksShoppingExample();
        Criteria criteria = example.createCriteria();
        criteria.andWorksIdEqualTo(worksId).andDeletedEqualTo(UserWorksShopping.NOT_DELETED);
        example.setOrderByClause(Column.ordered.asc());
        return dao.selectByExample(example);
    }

    public List<UserWorksShopping> queryByStorageId(String storageId) {
        UserWorksShoppingExample example = new UserWorksShoppingExample();
        Criteria criteria = example.createCriteria();
        criteria.andStorageIdEqualTo(storageId).andDeletedEqualTo(UserWorksShopping.NOT_DELETED);
        example.setOrderByClause(Column.ordered.asc());
        return dao.selectByExample(example);
    }

    public UserWorksShopping getById(Integer id) {
        return dao.selectByPrimaryKeyWithLogicalDelete(id, UserWorksShopping.NOT_DELETED);
    }

    /**
     * 我的橱窗-商品列表
     * 
     * @param userId
     * @param sorts
     * @param page
     * @return
     */
    public Pagination<QueryShopWindowGoodsDTO> queryShopWindowGoodsByUserId(Integer userId, Sorting[] sorts, Page page) {

        return Pagination.create(page,
            dao.countByUserId(userId),
            dao.queryByUserId(userId, Sortings.builder(sorts).toSql(), page));
    }

    public long queryShopWindowGoodsCountByUserId(Integer userId) {
        return dao.countByUserId(userId);
    }

    /**
     * 作品购物列表
     * 
     * @param worksId
     * @param sorts
     * @param page
     * @return
     */
    public Pagination<QueryShopWindowGoodsDTO> queryShopWindowGoodsByWorksId(Integer worksId, Sorting[] sorts, Page page) {

        return Pagination.create(page,
            dao.countByWorksId(worksId),
            dao.queryByWorksId(worksId, Sortings.builder(sorts).toSql(), page));
    }

    public void delete(UserWorksShopping record, String updateUser) {
        record.setDeleted(UserWorksShopping.IS_DELETED);
        record.setUpdateUser(updateUser);
        record.setUpdateTime(Date.from(Instant.now()));
        dao.updateByPrimaryKeySelective(record, Column.deleted, Column.updateUser, Column.updateTime);
    }

    public void deleteByWorksId(Integer worksId, String updateUser) {
        UserWorksShoppingExample example = new UserWorksShoppingExample();
        Criteria criteria = example.createCriteria();
        criteria.andWorksIdEqualTo(worksId).andDeletedEqualTo(UserWorksShopping.NOT_DELETED);
        List<UserWorksShopping> list = dao.selectByExample(example);
        if (Check.notNullOrEmpty(list)) {
            for (UserWorksShopping userWorksShopping : list) {
                userWorksShopping.setDeleted(UserWorksShopping.IS_DELETED);
                userWorksShopping.setUpdateUser(updateUser);
                userWorksShopping.setUpdateTime(Date.from(Instant.now()));
                dao.updateByPrimaryKeySelective(userWorksShopping,
                    Column.deleted,
                    Column.updateUser,
                    Column.updateTime);
            }
        }
    }

    public boolean getByOutsourcingGoodsId(Integer outsourcingGoodsId) {
        UserWorksShoppingExample example = new UserWorksShoppingExample();
        Criteria criteria = example.createCriteria();
        criteria.andGoodsIdEqualTo(outsourcingGoodsId).andDeletedEqualTo(UserWorksShopping.NOT_DELETED);
        List<UserWorksShopping> list = dao.selectByExample(example);
        return Check.isNullOrEmpty(list);
    }

    public boolean getByOutsourcingPackagedId(Integer outsourcingPackagedId) {
        UserWorksShoppingExample example = new UserWorksShoppingExample();
        Criteria criteria = example.createCriteria();
        criteria.andPackagedIdEqualTo(outsourcingPackagedId).andDeletedEqualTo(UserWorksShopping.NOT_DELETED);
        List<UserWorksShopping> list = dao.selectByExample(example);
        return Check.isNullOrEmpty(list);
    }
}